# -*- coding: cp1251 -*-
# imports
from math import sin, pi
from array import array
from random import random
import wave, winsound, sys, codecs
from Tkinter import *

# declaration
SR = 44100
NCHANNELS = 1
SWIDTH = 2
FRAME_RATE = 44100 * 2
NFRAMES = 44100
NSAMPLES = 44100
MAX_VAL = 32767

# classes
class String:
    def __init__(self, fr, SR, k):
        self.freq = fr
        self.N = SR / fr
        self.koef = k
    def pluck(self):
        self.buf = [random() - 0.5 for i in range(int(self.N))]
    def sample(self):
        val = self.buf[0]
        avg = self.koef * 0.5 * (self.buf[0] + self.buf[1])
        self.buf.append(avg)
        self.buf.pop(0)
        return val

#GUI
root = Tk()
frq = Entry(root, width = 30, bd = 4)
choice = IntVar()
choice.set(0)
rad0 = Radiobutton(root, text = "Normal", variable = choice, value = 0)
rad1 = Radiobutton(root, text = "Palm-Muted", variable = choice, value = 1)
rad2 = Radiobutton(root, text = "Chorus", variable = choice, value = 2)
freq = Scale(root, orient = HORIZONTAL, length = 500,
             from_ = 20, to = 1000, tickinterval = 980, resolution = 1)
but1 = Button(root, text = "Generate")
hold_button = Button(root, text = 'Hold')
exit_button = Button(root, text = "Quit")
text = Entry(root, width = 20, bd = 3)
text.insert(END, "Quantity of notes")
long_text = Text(root, width = 40, font = "Verdana 10", wrap = WORD)
samples = []
count = 0

# making of event - hold
def hold(event):
    global count
    global samples
    c = choice.get()
    if c == 1:
        koef = 0.85
        k = 0.5
    elif c == 0:
        koef = 0.999
        k = 2
    else:
        koef = 0.999
        k = 3
    count += 1
    cur_freq = freq.get()
    cur_str = String(cur_freq, SR, koef)
    help_str = String(cur_freq - cur_freq * 0.01, SR, koef)
    cur_str.pluck()
    help_str.pluck()
    sample = 0.0
    for i in range(int(NSAMPLES * k)):
        sample = cur_str.sample()
        if (c == 2):
            if (i > NSAMPLES / 64):
                sample += help_str.sample()
        samples.append(sample)
    if text.get() != '':
        text.delete(0, END)
    text.insert(END, count)
    
# making of event - generate
def rel(event):
    global count
    global samples
    #hold_button.invoke()
    tmpBuf = [int(x * MAX_VAL) for x in samples]
    data = array('h', tmpBuf).tostring()
    if long_text.get(0.0) != '':
        long_text.delete(0.1, END)
    long_text.insert(0.1, tmpBuf[:50])
    # making of the sound
    file = wave.open('death-melody.wav', 'wb')
    file.setparams((NCHANNELS, SWIDTH, FRAME_RATE, NFRAMES,
                    'NONE', 'noncompressed'))
    file.writeframes(data)
    file.close()
    winsound.PlaySound(u'death-melody.wav', winsound.SND_FILENAME)
    tmpBuf = []
    data = ""
    count = 0
    samples = []
    text.delete(0, END)
    text.insert(END, 0)
    
# making of event - exit\quit
def q(event):
    root.destroy()

but1.bind("<Button-1>", rel)
exit_button.bind("<Button-1>", q)
hold_button.bind("<Button-1>", hold)

freq.pack()
rad0.pack()
rad1.pack()
rad2.pack()
hold_button.pack()
but1.pack()
exit_button.pack()
text.pack()
long_text.pack()

root.mainloop()


